<?php

namespace App\Http\Controllers\Saas;

use App\Contract\OrderType;
use App\Http\Controllers\Controller;
use App\Http\Resources\PaginationCollection;
use App\Http\Service\AdaPayService;
use App\Http\Service\DeviceService;
use App\Jobs\CheckOrder;
use App\Jobs\PushMessage;
use App\Model\Agent;
use App\Model\AgentAmountLog;
use App\Model\Bill;
use App\Model\BillPay;
use App\Model\Business;
use App\Model\Device;
use App\Model\Message;
use App\Model\Order;
use App\Model\UserAmountLog;
use App\Model\UserRefund;
use App\Service\Baofu;
use App\User;
use App\Utils\Result;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\App;
use Illuminate\Support\Facades\Log;

class OrderController extends Controller
{
    public function refund(Request $request){
        $page = $request->input('page', 1);
        $perPage = $request->input('pageSize', 20);
        $status = $request->input('status');
        $orderNo = $request->input('order_no');
        $remark = $request->input('remark');
        $query = UserRefund::query();
        $query->when($orderNo, function($q) use ($orderNo) {
            $q->where('order_no', $orderNo);
        });
        if ($status != '') {
            $query->where('status', $status);
        }
        if($remark){
            $query->where('remark', 'like', '%'.$remark.'%');
        }
        $data = $query->orderByDesc('id')
            ->paginate($perPage, ['*'], 'page', $page);
        foreach($data as &$v){
            $v['error_msg'] = json_decode($v['error_msg'],true);
            if(!isset($v['errMsg'])){
                $v['errMsg'] = '无';
            }else{
                $v['error_msg'] = $v['errMsg'];
            }
        }
        return Result::success(new PaginationCollection($data));
    }

    public function index(Request $request)
    {
        $page = $request->input('page', 1);

        // Get the number of houses to show per page
        $perPage = $request->input('pageSize', 20);
        $keyword = $request->input('keyword');
        $status = $request->input('status');
        $start = $request->input('start');
        $end = $request->input('end');
        $type = $request->input('type');
        $pay_channel = $request->input('pay_channel');
        $recharge_status = $request->input('recharge_status');
        $busId = $request->input('businessId',0);
        $mobile = $request->input('mobile');
        $sn = $request->input('sn');
        $out_trade_id = $request->input('out_trade_id');
        $is_draw = $request->input('is_draw');
        $description = $request->input('description');
        $query = Order::query();
        $user = $this->getUser();
        if($user->roles != 'admin' ){
            if(!$mobile && !$sn){
                return Result::success([
                    'data' => ['items'=>[]],
                    'totalAmount' => 0,
                    'userCount'=>0,
                    'feeCount'=>0
                ]);
            }
            $is_draw = 0;
        }
        $query->when($description, function($q) use ($description) {
            $q->where('description', $description);
        });
        $query->when($keyword, function($q) use ($keyword) {
            $q->where('order_no', $keyword);
        });
        $query->when($is_draw, function($q) use ($is_draw) {
            $q->where('is_draw', $is_draw);
        });
        $query->when($out_trade_id, function($q) use ($out_trade_id) {
            $q->where('out_trade_id', $out_trade_id);
        });
        $query->when($type, function($q) use ($type) {
            $q->where('type', $type);
        });
        if ($status) {
            $query->where('status', $status);
        }

        if($mobile){
            $user = User::query()->where('mobile',$mobile)->first();
            if($user){
                $busId = Business::query()->where('user_id',$user->id)->value('id');
                $query->where('business_id',$busId);
            }

        }
        if($pay_channel){
            $query->where('pay_channel', $pay_channel);
        }
        if($start){
            $query->where('created_at','>=',$start.' 00:00:00');
        }
        if($end){
            $query->where('created_at','<=',$end.' 23:59:59');
        }
        if ($recharge_status != '') {
            $query->where('recharge_status', $recharge_status);
        }
        if ($sn) {
            $query->where('goods_desc','like','%'. $sn.'%');
        }
        if($busId){
            $query->where('business_id',$busId);
        }
        $data = $query->with(['house', 'user'])
            ->orderByDesc('id')
            ->paginate($perPage, ['*'], 'page', $page);
        foreach($data as &$v){
            $v['agent_id'] = Device::query()->where('id',$v['device_id'])->value('agent_id');
            if($v['agent_id']){
                $v['agent_name'] = Agent::query()->where('id',$v['agent_id'])->value('name');
            }else{
                $v['agent_name'] = '无';
            }
        }
        $query->where('status', 3);
        $totalAmount = $query->sum('pay_amt');
        $feeCount = $query->sum('fee');
        $userCount = $query->distinct('user_id')->count('user_id');
        return Result::success([
            'data' => new PaginationCollection($data),
            'totalAmount' => $totalAmount,
            'userCount'=>$userCount,
            'feeCount'=>$feeCount
        ]);
    }

    /**手动记账
     * @param Request $request
     * @return \Illuminate\Http\JsonResponse
     */
    public function handOrder(Request $request){
        $orderNo = $request->input('order_no');
        dispatch(new CheckOrder($orderNo,2))->delay(1);
        return Result::success();
    }


    public function drawOrder(Request $request){
        $orderNo = $request->input('order_no');
        $order = Order::query()->with('device', 'business', 'business.user', 'user')->where('order_no', $orderNo)->first();
        $service = app()->make(DeviceService::class);
        $user = User::query()->where('id', $order->user_id)->first();
        $service->addRechargeLog($order->device_id, $order->du, $order->pay_amt, $user,$order->paid_at);
        $amount = $order->pay_amt - $order->fee;
        if ($order->device_id) {
            $deviceModel = Device::query()->where('id', $order->device_id)->first();
            if ($deviceModel->agent_id) {
                $agentModel = Agent::query()->where('id', $deviceModel->agent_id)->first();
                $allRate = number_format($order->pay_amt * (Agent::MAX_RATE / 100), 2,'.', '');
                try {
                    if ($agentModel->pid) {
                        $firstAgent = Agent::query()->where('id', $agentModel->pid)->first();
                        $agentType = $firstAgent->type;
                    } else {
                        $firstAgent = $agentModel;
                        $agentType = $agentModel->type;
                    }
                    if ($agentType == 2) {
                        $firstFee = $deviceFee = number_format($firstAgent->service * $order->du, 2, '.', '');
                        if($firstAgent->rate > 0){
                            $deviceProfit = $amount*($firstAgent->rate/100);
                        }else{
                            $deviceProfit = 0;
                        }
                        $amount -= $deviceFee;
                        $firstFee= $deviceFee-$deviceProfit;
                        if ($agentModel->pid && $firstAgent->service > 0) {
                            $secondFee = number_format($firstFee * $agentModel->service / 100, 2, '.', '');
                            $firstFee -= $secondFee;
                            if($secondFee > 0) {
                                $agentModel->amount += $secondFee;
                                $agentModel->total_amount += $secondFee;
                                $agentModel->total_fee += $order->pay_amt;
                                $agentModel->save();
                                AgentAmountLog::create([
                                    'agent_id' => $agentModel->id,
                                    'type' => $order->type,
                                    'amount' => $secondFee,
                                    'order_id' => $order->id,
                                    'device_amount'=>$deviceFee,
                                    'log' => '设备管理费收入',
                                    'agent_type' => 2
                                ]);
                            }
                        }
                        if ($firstFee > 0) {
                            $firstAgent->amount += $firstFee;
                            $firstAgent->total_amount += $firstFee;
                            $firstAgent->total_fee += $order->pay_amt;
                            $firstAgent->save();
                            AgentAmountLog::create([
                                'agent_id' => $firstAgent->id,
                                'type' => $order->type,
                                'amount' => $firstFee,
                                'device_amount'=>$deviceFee,
                                'order_id' => $order->id,
                                'log' => '设备管理费收入',
                                'agent_type' => 2
                            ]);
                        }
                    } else {
                        if ($agentModel->rate) {
                            if ($agentModel->rate > 0.3) {
                                $agentModel->rate = 0.3;
                            }
                            $secAmount = number_format($order->pay_amt * $agentModel->rate / 100, 2, '.', '');
                            AgentAmountLog::create([
                                'agent_id' => $agentModel->id,
                                'type' => $order->type,
                                'amount' => $secAmount,
                                'order_id' => $order->id,
                                'log' => '电费充值（线上）分润收入'
                            ]);

                            $agentModel->amount += $secAmount;
                            $agentModel->total_amount += $secAmount;
                            $agentModel->total_fee += $order->pay_amt;
                            $agentModel->save();
                            $firstAmount = $allRate - $secAmount;
                            if ($firstAmount > 0 && $agentModel->pid) {
                                AgentAmountLog::create([
                                    'agent_id' => $firstAgent->id,
                                    'type' => $order->type,
                                    'amount' => $firstAmount,
                                    'order_id' => $order->id,
                                    'log' => '电费充值（线上）分润收入'
                                ]);
                                $firstAgent->amount += $secAmount;
                                $firstAgent->total_amount += $secAmount;
                                $firstAgent->total_fee += $order->pay_amt;
                                $firstAgent->save();
                            }
                        }
                    }
                } catch (\Exception $e) {

                }
            }
        }
        // 写入账单
        // 生成电费账单
        $bill = new Bill();
        if($order->device->type == 2){
            $type = OrderType::WATER;
            $title = '水费充值:'.$order->du.'吨';
        }else{
            $type = OrderType::ELECTRIC;
            $title = '电费充值:'.$order->du.'度';
        }
        $check = Bill::where('type',$type)
            ->where('paid_at',$order->paid_at)
            ->where('device_id',$order->device_id)
            ->first();
        if($check){
            return Result::success([]);
        }
        $bill->fill([
            'business_id' => $order->business_id,
            'mobile' => $order->user->mobile,
            'house_id' => $order->house_id,
            'device_id' => $order->device_id,
            'title' => $title,
            'amount' => $amount,
            'type' => $type,
            'is_paid' => 1,
            'paid_at' => $order->paid_at,
            'target_id'=>$order->id
            //'pay_date' => now()->toDateString(),
        ]);
        $bill->save();
        // 写入房东余额
        $fd = $order->business->user;
        $fd->amount += $amount;
        $fd->total_amount += $amount;
        $fd->save();
        //推送小程序信息
        if($fd->sub_1 == 1 && $fd->sub_status == 1 && $fd->openid){
            dispatch(new PushMessage($order,$fd->openid));
        }
        // 写入账户明细
        UserAmountLog::create([
            'user_id' => $fd->id,
            'type' => $order->type,
            'amount' => $amount,
            'order_id' => $order->id,
            'log' => '线上支付收入'
        ]);
        // 写入房东消息
        Message::create([
            'user_id' => $fd->id,
            'title' => '账单支付成功通知',
            'content' => '支付项目：' . $order->goods_desc . ' <br> 到账金额：￥' . $amount
        ]);

        $billPay = new BillPay();
        $payment = $order->pay_channel == 'wx_lite' ? 4 : 5;
        $billPay->fill([
            'sn' => $order->order_no,
            'bill_id' => $bill->id,
            'amount' => $amount,
            'payment' => $payment,
            'is_paid' => 1,
            'paid_at' => $order->paid_at,
        ]);
        $billPay->save();
        $order->is_draw = 0;
        $order->save();
        return Result::success([]);
    }

    /**订单退款
     * @param $id
     * @return void
     */
    public function cancelOrder(Request $request){
        $id = $request->input('id');
        $order = Order::query()->where('id',$id)->first();
        if(!$order->out_trade_id){
            return Result::error(1001,'该订单不可退款');
        }
        $refund_no = 'NR'.rand(99,999).$order->order_no;
        $amt = $request->input('amount');
        if(!$amt){
            return Result::success(1001,'请填写退款金额');
        }
        try{
            $save['order_no'] = $order->order_no;
            $save['payment_id'] = $order->payment_id;
            $save['amount'] = $amt;
            $save['type'] = $request->input('type',1);
            $save['remark'] = $request->input('remark','默认退款');
            $save['refund_no'] = $refund_no;
            $baofu = App::make(Baofu::class); // 通过容器解析依赖
            $result = $baofu->refund($save);
            $save['error_msg'] = json_encode($result);
            UserRefund::create($save);
            return Result::success();
        }catch (\Exception $e){
            return Result::error(1001,$e->getMessage());
        }

    }
}
